<?php
/**
 * Created by PhpStorm.
 * User: ytlmi
 * Date: 2018/4/18
 * Time: 9:48
 */

namespace app\snpdetection\controller;

use app\common\commonClass\ExcelImportTool;
use app\lab\controller\Person;
use org\util\wordtool\Word;
use org\util\forensictool\LittleTools;
use app\common\controller\BaseController;

class Sample extends BaseController
{
    protected $model = 'app\snpdetection\model\Sample';

    /**
     * @param string $sampleName
     * @throws \Exception
     * 下载报告
     */
    public function downloadReport($sampleName)
    {
        $this->makeReport($sampleName);
        $this->redirect('/report/snpdetection/' . $sampleName . '.docx');
    }

    //批量上传
    public function upload()
    {
        $model = new \app\snpdetection\model\Sample();
        try {
            // 获取表单上传文件 例如上传了001.jpg
            $file = request()->file('file');
            // 移动到框架应用根目录/public/uploads/ 目录下
            if ($file) {
                //保存文件
                $savePath = $_SERVER['DOCUMENT_ROOT'] . DS . 'uploads' . DS . 'snpsample';
                $info = $file->move($savePath);
                $filePath = $savePath . DS . $info->getSaveName();
                //解析文件
                $arr_header = ['sampleName'=>'Sample','genotype'=>'Call'];
                $construct = ['sampleName'=>'sampleName','genotype'=>'genotype'];
                $arr_require_always = ['sampleName','genotype'];//全程非空
                $data = ExcelImportTool::instance($filePath)->header($arr_header, $construct)->check($arr_require_always)->toSimpleArray();
                $samples = [];
                $sampleNames = [];
                foreach ($data as $datum) {
                    if (strpos($datum['sampleName'], ' ') !== false) {
                        $name = explode(' ', $datum['sampleName'])[0];
                    } else {
                        $name = $datum['sampleName'];
                    }
                    if (in_array($name, $sampleNames)) {
                        foreach ($samples as $index => $sample) {
                            if ($sample['sample_name'] == $name) {
                                $samples[$index]['genotype'][] = $datum['genotype'];
                            }
                        }
                    } else {
                        $sampleNames [] = $name;
                        $samples [] = ['sample_name' => $name, 'genotype' => [$datum['genotype']]];
                    }
                }
//                $option = input()['options'];
//                $id_disease = input()['id_disease'];
                $id_disease = 1;
                $option = [
                    'rs671'=>[
                        'sort'=>1,
                        'Allele 1'=>'GG',
                        'Allele 2'=>'AA',
                    ],
                    'rs1229984'=>[
                        'sort'=>0,
                        'Allele 1'=>'GG',
                        'Allele 2'=>'AA',
                    ]
                ];
                foreach ($samples as $index=>$sample) {
                    $samples[$index]['id_disease'] =$id_disease;
                    if (count($sample)<count($option)) return '样品'.$sample['sample_name'].'缺少位点信息';
                    foreach ($option as $allele=>$item) {
                        $item['Heterozygous'] = 'GA';
                        $samples[$index]['genotype'][$allele] = $item[$sample['genotype'][$item['sort']]];
                        unset($samples[$index]['genotype'][$item['sort']]);
                    }
                }
                $model->saveAll($samples);
            } else {
                return 123;
            }
        }catch (\Exception $e){
            return $e->getMessage();
        }
    }


        /**
     * @param string $sampleName
     * @throws \Exception
     * 生成报告
     */
    protected function makeReport($sampleName)
    {
        $replaceData = [];
        $startMark = '{';
        $endMark = '}';
        $riskMap=['正常','风险'];
        $sampleDataArr = $this->M->where(['sample_name' => $sampleName])->select();
        if (count($sampleDataArr)===0) throw new \Exception('样品名不存在或查询出错');//验证数据
        $sampleData = $sampleDataArr[0]->toArray();
        $diseaseId = $sampleData['id_disease'];//疾病ID
        $diseaseModel=new \app\snpdetection\model\Disease();
        $diseaseData = $diseaseModel->get($diseaseId)->toArray();//疾病数据数组
        $markers = $diseaseData['disease_marker'];//疾病包含的基因座数组
        $genotype = $sampleData['genotype'];//当前样品分型
        $markerM = new \app\snpdetection\model\Marker();

        //人员信息
        $replaceData['SAMPLE_NAME'] = $sampleData['sample_name'];
        $replaceData['SAMPLE_TYPE'] = $sampleData['sample_type'];
        $replaceData['PERSON_NAME'] = $sampleData['person_name'];
        $replaceData['PERSON_SEX'] = LittleTools::formatSex($sampleData['person_sex']);
        $replaceData['PERSON_ID'] = $sampleData['person_id'];
        $replaceData['PERSON_RACE'] = $sampleData['person_race'];

        //实验室信息
        $labPersonC = new Person();
        $config = Config::instance()->getConfig();
        $replaceData['OPERATOR'] = $labPersonC->getCol('name', ['id' => $sampleData['id_operator']]);
        $replaceData['AUDITOR'] = $labPersonC->getCol('name', ['id' => $sampleData['id_auditor']]);
        $replaceData['INST_NAME'] = $config['inst_name'];
        $replaceData['EQUIPMENT_NAME'] = $config['equipment_name'];
        $replaceData['EQUIPMENT_COMPANY'] = $config['equipment_company'];
        $replaceData['ANALYZE_SOFTWARE'] = $config['analyze_software'];
        //检测结果
        foreach ($markers as $markerId) {//遍历，完成表格
            $markerDataArr = $markerM->where(['id' => $markerId])->select();
            $markerData = $markerDataArr[0]->toArray();
            $markerName=$markerData['marker_name'];
            $markerNameUpper = strtoupper($markerName);
            $allele = [];
            foreach ($markerData['allele'] as $item) {
                $allele[$item['allele']]['risk'] = $item['risk'];
                $allele[$item['allele']]['describe'] = $item['describe'];
            }
            $replaceData[$markerNameUpper . '_ENZYME_NAME'] = $markerData['enzyme_name'];//编码酶名称
            $replaceData[$markerNameUpper . '_DESCRIBE'] = $markerData['marker_describe'];//基因座描述
            $replaceData[$markerNameUpper . '_GENOTYPE'] = $genotype[$markerName];//分型结果
            $replaceData[$markerNameUpper . '_RISK'] = $riskMap[$allele[$genotype[$markerName]]['risk']];//单位点风险
            $replaceData[$markerNameUpper . '_GENOTYPE_DESCRIBE'] = $allele[$genotype[$markerName]]['describe'];//当前分型描述

        }

        //分析结果
        $result = $this->judgement($sampleData, $diseaseData);
        $replaceData['RISK_NUM'] = $result['risk'];
        $replaceData['RISK_LEVEL'] = $result['level'];
        $replaceData['RISK_RESULT'] = $result['result'];

        //日期
        $replaceData['DATE'] = date('Y').'年'.date('m').'月'.date('d').'日';

        //替换
        $diseaseC = new Disease();
        $reportTemplate = $diseaseC->getTemplatePath() . '/' . $diseaseData['id'] . '.docx';
        $reportSavePath = $diseaseC->getReportPath() . '/' . $sampleName . '.docx';
        $rep = [];
        foreach ($replaceData as $mark => $value) {
            $rep[$startMark . $mark . $endMark] = $value;
        }
        Word::instance()->setTemplate($rep, $reportTemplate, $reportSavePath);
    }

    /**
     * @param array $sampleData
     * @param array $diseaseData
     * @return array
     * @throws \Exception
     * 结果判定
     */
    protected function judgement($sampleData, $diseaseData)
    {
        $genotype = $sampleData['genotype'];//当前样品分型
        $markers = $diseaseData['disease_marker'];//疾病包含的基因座数组
        $riskRole = $diseaseData['risk_role'];
        $levelRole = $diseaseData['level_role'];
        $resultRole = $diseaseData['result_role'];
        $markerM = new \app\snpdetection\model\Marker();
        //RISK
        $risk = 0;
        foreach ($riskRole as $situation) {//遍历匹配结果
            foreach ($markers as $markerId) {
                $markerDataArr = $markerM->where(['id' => $markerId])->select();
                $markerData = $markerDataArr[0]->toArray();
                $markerName=$markerData['marker_name'];
                if (!$this->compareAllele($situation[$markerName], $genotype[$markerName])) {
                    continue 2;//外层循环跳过一个
                }
            }
            $risk = $situation['risk'];
        }

        //LEVEL
        $level = 0;
        foreach ($levelRole as $levelNum => $point) {
            if ($risk <= $point) {
                $level = $levelNum;
                break;
            }
        }

        //RESULT
        $result = '';
        foreach ($resultRole as $point) {
            if ($level <= $point['topLevel']) {
                $result = $point['result'];
                break;
            }
        }

        return [
            'risk' => $risk,
            'level' => LittleTools::instance()->numToZh($level) . '级',
            'result' => $result
        ];
    }

    //比较两个分型是否相同
    protected function compareAllele($allele0, $allele1)
    {
        if (strlen($allele0) === strlen($allele1) && strlen($allele0) === 2) {
            $allele0_0 = substr($allele0, 0, 1);
            $allele0_1 = substr($allele0, 1, 1);
            $allele1_0 = substr($allele1, 0, 1);
            $allele1_1 = substr($allele1, 1, 1);
            if (($allele0_0 === $allele1_0 && $allele0_1 === $allele1_1) || ($allele0_0 === $allele1_1 && $allele0_1 === $allele1_0)) {
                return true;
            } else {
                return false;
            }
        } else {
            return false;
        }
    }

}